package com.ruoyi.listener.losses;

import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.util.ObjectUtil;
import com.alibaba.excel.context.AnalysisContext;
import com.alibaba.excel.event.AnalysisEventListener;
import com.ruoyi.common.Rejectsn;
import com.ruoyi.common.excel.ExcelListener;
import com.ruoyi.common.excel.ExcelResult;
import com.ruoyi.common.exception.ServiceException;
import com.ruoyi.common.helper.LoginHelper;
import com.ruoyi.common.utils.ValidatorUtils;
import com.ruoyi.common.utils.spring.SpringUtils;
import com.ruoyi.quality.domain.bo.QualityRejectsnLossesBo;
import com.ruoyi.quality.domain.vo.QualityRejectsnLossesImportVo;
import com.ruoyi.quality.domain.vo.QualityRejectsnLossesVo;
import com.ruoyi.quality.service.IQualityRejectsnLossesService;

import java.math.BigDecimal;
import java.math.RoundingMode;
import java.util.List;
import java.util.Objects;

import static com.ruoyi.common.core.mapper.BaseMapperPlus.log;

public class RejectsnLossesImportListener extends AnalysisEventListener<QualityRejectsnLossesImportVo> implements ExcelListener<QualityRejectsnLossesImportVo> {
    private final IQualityRejectsnLossesService rejectsnLossesService;
    private final Boolean isUpdateSupport;
    private final String operName;
    private int successNum = 0;
    private int failureNum = 0;
    private final StringBuilder successMsg = new StringBuilder();
    private final StringBuilder failureMsg = new StringBuilder();

    public RejectsnLossesImportListener(Boolean isUpdateSupport) {
        this.rejectsnLossesService = SpringUtils.getBean(IQualityRejectsnLossesService.class);
        this.isUpdateSupport = isUpdateSupport;
        this.operName = LoginHelper.getUsername();
    }

    @Override
    public ExcelResult<QualityRejectsnLossesImportVo> getExcelResult() {
        return new ExcelResult<QualityRejectsnLossesImportVo>() {

            @Override
            public String getAnalysis() {
                if (failureNum > 0) {
                    failureMsg.insert(0, "很抱歉，导入失败！共 " + failureNum + " 条数据格式不正确，错误如下：");
                    throw new ServiceException(failureMsg.toString());
                } else {
                    successMsg.insert(0, "恭喜您，数据已全部导入成功！共 " + successNum + " 条，数据如下：");
                }
                return successMsg.toString();
            }

            @Override
            public List<QualityRejectsnLossesImportVo> getList() {
                return null;
            }

            @Override
            public List<String> getErrorList() {
                return null;
            }
        };
    }

    @Override
    public void invoke(QualityRejectsnLossesImportVo qualityRejectsnLossesVo, AnalysisContext analysisContext) {
        String oddNumber = qualityRejectsnLossesVo.getOddNumber();
        QualityRejectsnLossesVo rejectsnLossesVo = this.rejectsnLossesService.queryByOddNumber(oddNumber);

        String dept = qualityRejectsnLossesVo.getDeptAbbreviation();
        if (dept == null || dept.isEmpty()){
            qualityRejectsnLossesVo.setDeptAbbreviation(Rejectsn.DEPT_DEFAULT);
        }
        String orderUnit = qualityRejectsnLossesVo.getOrderUnit();
        if (orderUnit == null || orderUnit.isEmpty()){
            qualityRejectsnLossesVo.setOrderUnit(Rejectsn.ORDER_UNIT);
        }

        try {
            // 验证是否存在这个信息单号
            if (ObjectUtil.isNull(rejectsnLossesVo)) {

                try {
                    String contractNumber = qualityRejectsnLossesVo.getContractNumber();
                    String prefix = contractNumber + "-";
                    String partNumber = qualityRejectsnLossesVo.getPartNumber().replaceAll("\\s","");
                    if (partNumber.startsWith(prefix)){
                        partNumber = partNumber.substring(prefix.length());
                    }

                    if (partNumber.endsWith("/R") || partNumber.endsWith("/r")){
                        partNumber = partNumber.substring(0,partNumber.length()-2);
                    }

                    qualityRejectsnLossesVo.setPartNumber(partNumber);
                    qualityRejectsnLossesVo.setProjectNumber(prefix + partNumber);
                } catch (Exception e) {
                    throw new RuntimeException(e);
                }

                String conclusion = qualityRejectsnLossesVo.getHandlingConclusion();
                String wkHours = null;
                if (conclusion != null) {
                    switch (conclusion) {
                        case Rejectsn.Reuse:
                            wkHours = qualityRejectsnLossesVo.getReuseHours() != null ? qualityRejectsnLossesVo.getReuseHours() : "";
                            break;
                        case Rejectsn.Repair:
                            wkHours = qualityRejectsnLossesVo.getRepairHours() != null ? qualityRejectsnLossesVo.getRepairHours() : "";
                            break;
                        case Rejectsn.Rework:
                            wkHours = qualityRejectsnLossesVo.getReworkHours() != null ? qualityRejectsnLossesVo.getReworkHours() : "";
                            break;
                        default:
                            // 设置默认值
                            wkHours = Rejectsn.WK_HOURS;
                            break;
                    }
                }else {
                    qualityRejectsnLossesVo.setHandlingConclusion(Rejectsn.Unfinished);
                }
                BigDecimal workingHours;
                if (wkHours == null || wkHours.trim().isEmpty() || wkHours.equals("0")) {
                    workingHours = new BigDecimal(Rejectsn.WK_HOURS);
                } else {
                    workingHours = new BigDecimal(wkHours);
                }
                qualityRejectsnLossesVo.setWorkingHours(workingHours);

                QualityRejectsnLossesBo rejectsnLossesBo = BeanUtil.toBean(qualityRejectsnLossesVo, QualityRejectsnLossesBo.class);
                ValidatorUtils.validate(rejectsnLossesBo);
                rejectsnLossesBo.setCreateBy(operName);
                rejectsnLossesService.insertByBo(rejectsnLossesBo);
                successNum++;
                successMsg.append("<br/>").append(successNum).append("、信息单号 ").append(rejectsnLossesBo.getOddNumber()).append(" 导入成功");
            } else if (isUpdateSupport) {

                BigDecimal lossAmount;
                if (Objects.equals(dept, Rejectsn.DEPT_HEAT)){
                    qualityRejectsnLossesVo.setUnitPrice(new BigDecimal(Rejectsn.RPrice));
                    lossAmount = rejectsnLossesVo.getWeight().multiply(new BigDecimal(Rejectsn.RPrice)).divide(new BigDecimal(1000), 10, RoundingMode.HALF_UP);
                }else {
                    qualityRejectsnLossesVo.setUnitPrice(new BigDecimal(Rejectsn.HPrice));
                    lossAmount = rejectsnLossesVo.getWorkingHours().multiply(new BigDecimal(Rejectsn.HPrice));
                }

                qualityRejectsnLossesVo.setLossAmount(lossAmount);
                Long rejectsnId = rejectsnLossesVo.getRejectsnId();
                QualityRejectsnLossesBo rejectsnLossesBo = BeanUtil.toBean(qualityRejectsnLossesVo, QualityRejectsnLossesBo.class);
                rejectsnLossesBo.setRejectsnId(rejectsnId);
                ValidatorUtils.validate(rejectsnLossesBo);
                rejectsnLossesBo.setUpdateBy(operName);
                rejectsnLossesService.updateByBo(rejectsnLossesBo);
                successNum++;
                successMsg.append("<br/>").append(successNum).append("、信息单号 ").append(rejectsnLossesBo.getOddNumber()).append(" 更新成功");
            } else {
                failureNum++;
                failureMsg.append("<br/>").append(failureNum).append("、信息单号 ").append(qualityRejectsnLossesVo.getOddNumber()).append(" 已存在");
            }
        } catch (Exception e) {
            failureNum++;
            String msg = "<br/>" + failureNum + "、信息单号 " + qualityRejectsnLossesVo.getOddNumber() + " 导入失败：";
            failureMsg.append(msg).append(e.getMessage());
            log.error(msg, e);
        }
    }

    @Override
    public void doAfterAllAnalysed(AnalysisContext analysisContext) {

    }
}
